/**
 * Copyright (c) 2018-2021, BookOS Development Team
 * SPDX-License-Identifier: Apache-2.0
 * 
 * Contains: Interrupt
 * 
 * Change Logs:
 * Date           Author            Notes
 * 2021-12-03     JasonHu           Init
 */

#define __ASSEMBLY__
#include <Context.h>
#include <Regs.h>

.text

.extern IRQ_DelayQueueCheck
.extern TrapDispatch
.extern TrapSwitchStack
.extern ReSchedCheck

.extern BootStackTop

.globl TrapEntry
.align 2 # TrapEntry must aligin with 4 byte
TrapEntry:
    /* save sp to sscratch reg, sscratch saved old sp from user/kernel */
    csrrw sp, sscratch, sp
    
    /* switch to cpu stack as temp stack */
    la sp, BootStackTop

    /* save context to cpu stack */
    SAVE_CONTEXT

    /* switch stack from CPU stack to thread stack */
    mv a0, sp
    call TrapSwitchStack
    mv sp, a0 /* a0 saved new stack */

    /* call handler */
    mv a0, sp
    call TrapDispatch
    
    /* only external IRQ and timer IRQ check IRQ queue */
    csrr t0, scause
    li t1, SCAUSE_INTERRUPT
    and t0, t0, t1
    beqz t0, TrapReturn /* No interrupt bit */

    /* do IRQ queue check */
    call IRQ_DelayQueueCheck

    /* check sched */
    call ReSchedCheck

    tail TrapReturn

.globl TrapReturn
TrapReturn:
    
    /* restore context will restore sp */
    RESTORE_CONTEXT
    /* return from supervisor call */
    sret
